var gulp        = require('gulp'),
    nodemon     = require('gulp-nodemon'),
    plumber     = require('gulp-plumber'),
    livereload  = require('gulp-livereload'),
    uglify      = require('gulp-uglify'),
    sass        = require('gulp-sass'),
    concat      = require('gulp-concat'),
    rename      = require('gulp-rename'),
    rev         = require('gulp-rev'),
    flatten     = require('gulp-flatten'),
    htmlmin     = require('gulp-minify-html'),
    es          = require('event-stream'),
    parse       = require('esprima').parse,
    toString    = require('escodegen').generate,
    confusion   = require('confusion'),
    fs          = require('fs'),
    path        = require('path'),
    runSequence = require('run-sequence'),
    jshint      = require('gulp-jshint'),
    stylish     = require('jshint-stylish'),
    gulpif      = require('gulp-if'),
    del         = require('del'),
    browserSync = require('browser-sync').create(),
    revCollector = require('gulp-rev-collector'),
    config = require('./config/config'),
    SceneVariable=config.app.name,
    paths = {
        pages: './app/views/**/*',
        sass: './asset/sass/**/*.scss',
        font: './asset/font/*',
        images: './asset/images/**/*',
        script: './asset/js/**/*.js',
        minifyjs: './asset/js/**/*.js',
        json: './asset/json/**/*',
        componentImg: './asset/component/**/img/*',
        componentHtml: './asset/component/**/*.html',
        componentJs: './asset/component/**/*.js',
        componentScss: './asset/component/**/*.scss',
        componentCss: './asset/component/**/*.css',
        revPath: './public/revpath/'
    };
var confusionGulp = function () {
    return es.map(function (file, callback) {
        if (file.isNull()) {
            return callback(null, file);
        }
        var ast = parse(fs.readFileSync(file.path));
        var obfuscated = confusion.transformAst(ast, confusion.createVariableName);
        file.contents = new Buffer(toString(obfuscated));
        return callback(null, file);
    });
}

// 音频文件
gulp.task('json', function () {
    gulp.src(paths.json)
        .pipe(gulp.dest('./public/json'));
});
// 图片
gulp.task('images', function() {
    if(SceneVariable=='development'){
        gulp.src(paths.images)
            .pipe(gulp.dest('./public/images'));
    }else{
        gulp.src(paths.images)
            .pipe(rev())
            .pipe(gulp.dest('./public/images'))
            .pipe(rev.manifest())
            .pipe(gulp.dest(paths.revPath+'/images'));
    }
});
// 字体文件
gulp.task('font', function () {
    if(SceneVariable=='development'){
        gulp.src(paths.font)
            .pipe(gulp.dest('./public/font'))
    }else {
        gulp.src(paths.font)
            .pipe(rev())
            .pipe(gulp.dest('./public/font'))
            .pipe(rev.manifest())                           // 生成版本号地图
            .pipe(gulp.dest(paths.revPath + '/font'));
    }
});

// 公用组件
gulp.task('component', function() {
    if (SceneVariable == 'development') {
        gulp.src(paths.componentImg)
            .pipe(gulp.dest('./public/component'));
        gulp.src(paths.componentHtml)
            .pipe(gulp.dest('./public/component'));
        gulp.src(paths.componentJs)
            .pipe(gulp.dest('./public/component'));
        gulp.src(paths.componentCss)
            .pipe(gulp.dest('./public/component'));
        gulp.src(paths.componentScss)
            .pipe(plumber())
            .pipe(sass({outputStyle: 'compressed'}))
            .pipe(gulp.dest('./public/component'));
    } else {
        gulp.src(paths.componentImg)
            .pipe(rev())
            .pipe(gulp.dest('./public/component'))
            .pipe(rev.manifest())
            .pipe(gulp.dest(paths.revPath + '/component/img'));
        gulp.src(paths.componentHtml)
            .pipe(rev())
            .pipe(gulp.dest('./public/component'))
            .pipe(rev.manifest())
            .pipe(gulp.dest(paths.revPath + '/component/html'));
        gulp.src(paths.componentJs)
            .pipe(uglify({
                mangle: true,
                output: {
                    beautify: true
                },
                compress: true
            }))
            .pipe(confusionGulp())
            .pipe(uglify())
            .pipe(rev())
            .pipe(gulp.dest('./public/component'))
            .pipe(rev.manifest())
            .pipe(gulp.dest(paths.revPath + '/component/js'));
        gulp.src(paths.componentCss)
            .pipe(rev())
            .pipe(gulp.dest('./public/component'))
            .pipe(rev.manifest())
            .pipe(gulp.dest(paths.revPath + '/component/css'));
        gulp.src(paths.componentScss)
            .pipe(plumber())
            .pipe(sass({outputStyle: 'compressed'}))
            .pipe(rev())
            .pipe(gulp.dest('./public/component'))
            .pipe(rev.manifest())
            .pipe(gulp.dest(paths.revPath + '/component/scss'));
    }
});
// sass
gulp.task('sass', function () {
    if (SceneVariable == 'development') {
        gulp.src(paths.sass)
            .pipe(plumber())
            .pipe(sass({outputStyle: 'compressed'}))
            .pipe(gulp.dest('./public/css'));
    } else {
        gulp.src([paths.sass,'!./asset/sass/**/alert.scss'])
            .pipe(plumber())
            .pipe(sass({outputStyle: 'compressed'}))
            .pipe(rev())
            .pipe(gulp.dest('./public/css'))
            .pipe(rev.manifest())
            .pipe(gulp.dest(paths.revPath + '/css'));
        gulp.src(['./asset/sass/**/alert.scss'])
            .pipe(plumber())
            .pipe(sass({outputStyle: 'compressed'}))
            .pipe(gulp.dest('./public/css'));
    }
});
// 压缩js任务
gulp.task('minifyjs', function() {
    if (SceneVariable == 'development') {
        return gulp.src(paths.minifyjs)
            .pipe(gulp.dest('./public/js'));             // 压缩之后的css文件输出目录
    } else {
        gulp.src([paths.minifyjs,'!./asset/js/**/config.js','!./asset/js/**/config-*.js','!./asset/js/**/common.js'])
            .pipe(uglify({
                mangle: true,
                output: {
                    beautify: true
                },
                compress: true
            }))
            .pipe(confusionGulp())
            .pipe(uglify())
            .pipe(rev())                                    // 生成相关版本号
            .pipe(gulp.dest('./public/js'))                 // 压缩之后的css文件输出目录
            .pipe(rev.manifest())                           // 生成版本号地图
            .pipe(gulp.dest(paths.revPath + '/js'));        // 输出地图文件目录
        // 编译不同环境下的配置文件
        gulp.src(['./asset/js/**/config.js','./asset/js/**/config-*.js','./asset/js/**/common.js'])
            .pipe(uglify({
                mangle: true,
                output: {
                    beautify: true
                },
                compress: true
            }))
            .pipe(confusionGulp())
            .pipe(uglify())
            .pipe(gulp.dest('./public/js'));                // 压缩之后的css文件输出目录
    }
});
// 公用组件
gulp.task('pages', function() {
    return gulp.src(paths.pages)
        .pipe(gulpif(
            true, htmlmin({
                empty: true,
                spare: true,
                quotes: true
            })
        ))
        .pipe(gulp.dest('./pages/views'));
});
gulp.task('Rev', function () {
    gulp.src([paths.revPath + '**/*.json','./public/**/*','!./public/images/**/*',
        '!./public/font/**/*.ttf',
        '!./public/font/**/*.eot',
        '!./public/font/**/*.woff',
        '!./public/font/**/*.svg'])
        .pipe(revCollector())
        .pipe(gulp.dest('./public'));
    gulp.src([paths.revPath + '**/*.json','./pages/**/*'])
        .pipe(revCollector())
        .pipe(gulp.dest('./pages'));
});

gulp.task('del', function () {
    del.sync(['./public']);
    del.sync(['./pages']);
});
gulp.task('delRev', function () {
    del.sync([paths.revPath]);
});

gulp.task('watch', function() {
    gulp.watch(paths.json, ['json']);
    gulp.watch(paths.images, ['images']);
    gulp.watch(paths.font, ['font']);
    gulp.watch(paths.sass, ['sass']);
    gulp.watch(paths.componentHtml, ['component']);
    gulp.watch(paths.componentJs, ['component']);
    gulp.watch(paths.componentScss, ['component']);
    gulp.watch(paths.script, ['minifyjs']);
    gulp.watch(paths.pages, ['pages']);
});

// 开发构建
gulp.task('dev', function (done) {
    SceneVariable = 'development';
    runSequence(
        ['del'],
        ['json', 'images', 'font', 'sass', 'component', 'minifyjs', 'pages'],
        ['watch'],
        done);
});

// 测试构建
gulp.task('test', function (done) {
    SceneVariable = 'test';
    runSequence(
        ['del'],
        ['json', 'images', 'font', 'sass', 'component', 'minifyjs', 'pages'],
        ['Rev'],
        done);
});

// 线上构建
gulp.task('production', function (done) {
    SceneVariable = 'production';
    runSequence(
        ['del'],
        ['json', 'images', 'font', 'sass', 'component', 'minifyjs', 'pages'],
        ['Rev'],
        done);
});

// 根据环境变量自动构建
gulp.task('accord', function (done) {
    if(SceneVariable=='development'){
        runSequence(
            ['del'],
            ['json', 'images', 'font', 'sass', 'component', 'minifyjs', 'pages'],
            ['watch'],
            done);
    }else{
        runSequence(
            ['del'],
            ['json', 'images', 'font', 'sass', 'component', 'minifyjs', 'pages'],
            ['Rev'],
            done);
    }
});
